const DatabaseService = require('./DatabaseService');
const StockService = require('./StockService');
// 移除对 StockHistoryService 的直接引用，避免循环依赖

class StrategyService {
  // 创建策略
  static async createStrategy(userId, name, description, config) {
    try {
      // 验证配置
      if (!name || !config) {
        throw new Error('Strategy name and configuration are required');
      }

      const strategy = DatabaseService.createStrategy(userId, name, description, config);
      return strategy;
    } catch (error) {
      throw new Error(`Failed to create strategy: ${error.message}`);
    }
  }

  // 获取用户的所有策略
  static async getStrategiesByUserId(userId) {
    try {
      const strategies = DatabaseService.getStrategiesByUserId(userId);
      return strategies;
    } catch (error) {
      throw new Error(`Failed to get strategies: ${error.message}`);
    }
  }

  // 获取特定策略
  static async getStrategyById(id) {
    try {
      const strategy = DatabaseService.getStrategyById(id);
      if (!strategy) {
        throw new Error('Strategy not found');
      }
      return strategy;
    } catch (error) {
      throw new Error(`Failed to get strategy: ${error.message}`);
    }
  }

  // 更新策略
  static async updateStrategy(id, name, description, config, isActive) {
    try {
      const strategy = DatabaseService.updateStrategy(id, name, description, config, isActive);
      return strategy;
    } catch (error) {
      throw new Error(`Failed to update strategy: ${error.message}`);
    }
  }

  // 删除策略
  static async deleteStrategy(id) {
    try {
      DatabaseService.deleteStrategy(id);
      return { success: true, message: 'Strategy deleted successfully' };
    } catch (error) {
      throw new Error(`Failed to delete strategy: ${error.message}`);
    }
  }

  // 执行移动平均线策略
  static async executeMovingAverageStrategy(userId, symbol, shortPeriod = 5, longPeriod = 20) {
    try {
      // 动态引入 StockHistoryService 以避免循环依赖
      const StockHistoryService = require('./StockHistoryService');
      
      // 从数据库获取历史数据（如果数据库中没有则从API获取并存储）
      const historicalData = await StockHistoryService.getHistoricalData(symbol, 'daily', longPeriod * 2);
      console.log("-历史数据-->",historicalData)
      // 确保有足够的数据
      if (historicalData.length < longPeriod) {
        throw new Error('Not enough historical data for the specified periods');
      }
      
      // 只取最近的数据
      const recentData = historicalData.slice(-longPeriod * 2).map(item => ({
        date: new Date(item.date),
        open: item.open,
        high: item.high,
        low: item.low,
        close: item.close,
        volume: item.volume
      }));
      
      // 计算移动平均线
      const shortMA = this.calculateMovingAverage(recentData, shortPeriod);
      const longMA = this.calculateMovingAverage(recentData, longPeriod);
      
      // 获取最新价格
      const currentPrice = recentData[recentData.length - 1].close;
      
      // 策略逻辑：当短期均线穿越长期均线时发出信号
      const shortMAPrev = shortMA[shortMA.length - 2];
      const shortMACurrent = shortMA[shortMA.length - 1];
      const longMAPrev = longMA[longMA.length - 2];
      const longMACurrent = longMA[longMA.length - 1];
      
      let signal = 'HOLD'; // 默认持有
      
      // 买入信号：短期均线上穿长期均线
      if (shortMAPrev <= longMAPrev && shortMACurrent > longMACurrent) {
        signal = 'BUY';
      }
      // 卖出信号：短期均线下穿长期均线
      else if (shortMAPrev >= longMAPrev && shortMACurrent < longMACurrent) {
        signal = 'SELL';
      }
      
      return {
        symbol: symbol,
        currentPrice: currentPrice,
        shortMA: shortMACurrent,
        longMA: longMACurrent,
        signal: signal,
        timestamp: new Date()
      };
    } catch (error) {
      // 不再使用模拟数据回退，直接抛出错误
      console.error(`Failed to execute moving average strategy: ${error.message}`);
      throw new Error(`Failed to execute moving average strategy: ${error.message}`);
    }
  }

  // 执行RSI策略
  static async executeRSIStrategy(symbol, period = 14, overbought = 70, oversold = 30) {
    try {
      // 动态引入 StockHistoryService 以避免循环依赖
      const StockHistoryService = require('./StockHistoryService');
      
      // 从数据库获取历史数据（如果数据库中没有则从API获取并存储）
      const historicalData = await StockHistoryService.getHistoricalData(symbol, 'daily', period * 3);
      
      // 确保有足够的数据
      if (historicalData.length < period * 3) {
        throw new Error('Not enough historical data for RSI calculation');
      }
      
      // 只取最近的数据
      const recentData = historicalData.slice(-period * 3).map(item => ({
        date: new Date(item.date),
        open: item.open,
        high: item.high,
        low: item.low,
        close: item.close,
        volume: item.volume
      }));
      
      // 计算RSI
      const rsi = this.calculateRSI(recentData, period);
      const currentRSI = rsi[rsi.length - 1];
      const currentPrice = recentData[recentData.length - 1].close;
      
      let signal = 'HOLD';
      
      // 超卖区域买入信号
      if (currentRSI < oversold) {
        signal = 'BUY';
      }
      // 超买区域卖出信号
      else if (currentRSI > overbought) {
        signal = 'SELL';
      }
      
      return {
        symbol: symbol,
        currentPrice: currentPrice,
        rsi: currentRSI,
        signal: signal,
        overbought: overbought,
        oversold: oversold,
        timestamp: new Date()
      };
    } catch (error) {
      // 不再使用模拟数据回退，直接抛出错误
      console.error(`Failed to execute RSI strategy: ${error.message}`);
      throw new Error(`Failed to execute RSI strategy: ${error.message}`);
    }
  }

  // 执行布林带策略
  static async executeBollingerBandsStrategy(symbol, period = 20, multiplier = 2) {
    try {
      // 动态引入 StockHistoryService 以避免循环依赖
      const StockHistoryService = require('./StockHistoryService');
      
      // 从数据库获取历史数据（如果数据库中没有则从API获取并存储）
      const historicalData = await StockHistoryService.getHistoricalData(symbol, 'daily', period * 2);
      
      // 确保有足够的数据
      if (historicalData.length < period * 2) {
        throw new Error('Not enough historical data for Bollinger Bands calculation');
      }
      
      // 只取最近的数据
      const recentData = historicalData.slice(-period * 2).map(item => ({
        date: new Date(item.date),
        open: item.open,
        high: item.high,
        low: item.low,
        close: item.close,
        volume: item.volume
      }));
      
      // 计算布林带
      const bb = this.calculateBollingerBands(recentData, period, multiplier);
      
      // 获取最新价格
      const currentPrice = recentData[recentData.length - 1].close;
      const upperBand = bb.upper[bb.upper.length - 1];
      const lowerBand = bb.lower[bb.lower.length - 1];
      const middleBand = bb.middle[bb.middle.length - 1];
      
      let signal = 'HOLD';
      
      // 买入信号：价格触及下轨
      if (currentPrice <= lowerBand) {
        signal = 'BUY';
      }
      // 卖出信号：价格触及上轨
      else if (currentPrice >= upperBand) {
        signal = 'SELL';
      }
      
      return {
        symbol: symbol,
        currentPrice: currentPrice,
        upperBand: upperBand,
        middleBand: middleBand,
        lowerBand: lowerBand,
        signal: signal,
        timestamp: new Date()
      };
    } catch (error) {
      // 不再使用模拟数据回退，直接抛出错误
      console.error(`Failed to execute Bollinger Bands strategy: ${error.message}`);
      throw new Error(`Failed to execute Bollinger Bands strategy: ${error.message}`);
    }
  }

  // 执行海龟交易策略
  static async executeTurtleTradingStrategy(symbol, entryPeriod = 20, exitPeriod = 10) {
    try {
      // 动态引入 StockHistoryService 以避免循环依赖
      const StockHistoryService = require('./StockHistoryService');
      
      // 海龟交易策略需要足够多的历史数据
      const requiredDataLength = Math.max(entryPeriod, exitPeriod) + 10;
      const historicalData = await StockHistoryService.getHistoricalData(symbol, 'daily', requiredDataLength);
      
      // 确保有足够的数据
      if (historicalData.length < requiredDataLength) {
        throw new Error('Not enough historical data for Turtle Trading strategy calculation');
      }
      
      // 只取最近的数据
      const recentData = historicalData.slice(-requiredDataLength).map(item => ({
        date: new Date(item.date),
        open: item.open,
        high: item.high,
        low: item.low,
        close: item.close,
        volume: item.volume
      }));
      
      // 计算唐奇安通道
      const donchianChannels = this.calculateDonchianChannels(recentData, entryPeriod, exitPeriod);
      
      // 获取最新价格
      const currentPrice = recentData[recentData.length - 1].close;
      const entryUpper = donchianChannels.entryUpper[donchianChannels.entryUpper.length - 1];
      const entryLower = donchianChannels.entryLower[donchianChannels.entryLower.length - 1];
      const exitUpper = donchianChannels.exitUpper[donchianChannels.exitUpper.length - 1];
      const exitLower = donchianChannels.exitLower[donchianChannels.exitLower.length - 1];
      
      let signal = 'HOLD';
      
      // 海龟交易策略信号逻辑：
      // 1. 入市信号：价格突破唐奇安通道上轨（买入）或下轨（卖出）
      // 2. 出市信号：价格反向突破较短周期的唐奇安通道
      
      // 买入信号：价格突破入市通道上轨
      if (currentPrice > entryUpper) {
        signal = 'BUY';
      }
      // 卖出信号：价格突破入市通道下轨
      else if (currentPrice < entryLower) {
        signal = 'SELL';
      }
      
      return {
        symbol: symbol,
        currentPrice: currentPrice,
        entryUpper: entryUpper,
        entryLower: entryLower,
        exitUpper: exitUpper,
        exitLower: exitLower,
        signal: signal,
        timestamp: new Date()
      };
    } catch (error) {
      // 不再使用模拟数据回退，直接抛出错误
      console.error(`Failed to execute Turtle Trading strategy: ${error.message}`);
      throw new Error(`Failed to execute Turtle Trading strategy: ${error.message}`);
    }
  }

  // 计算唐奇安通道（海龟交易策略核心指标）
  static calculateDonchianChannels(data, entryPeriod, exitPeriod) {
    const entryUpper = [];
    const entryLower = [];
    const exitUpper = [];
    const exitLower = [];
    
    // 计算入市通道（较长周期）
    for (let i = entryPeriod - 1; i < data.length; i++) {
      let highestHigh = data[i - entryPeriod + 1].high;
      let lowestLow = data[i - entryPeriod + 1].low;
      
      for (let j = 1; j < entryPeriod; j++) {
        if (data[i - j].high > highestHigh) {
          highestHigh = data[i - j].high;
        }
        if (data[i - j].low < lowestLow) {
          lowestLow = data[i - j].low;
        }
      }
      
      entryUpper.push(highestHigh);
      entryLower.push(lowestLow);
    }
    
    // 计算出市通道（较短周期）
    for (let i = exitPeriod - 1; i < data.length; i++) {
      let highestHigh = data[i - exitPeriod + 1].high;
      let lowestLow = data[i - exitPeriod + 1].low;
      
      for (let j = 1; j < exitPeriod; j++) {
        if (data[i - j].high > highestHigh) {
          highestHigh = data[i - j].high;
        }
        if (data[i - j].low < lowestLow) {
          lowestLow = data[i - j].low;
        }
      }
      
      exitUpper.push(highestHigh);
      exitLower.push(lowestLow);
    }
    
    return { entryUpper, entryLower, exitUpper, exitLower };
  }

  // 计算布林带指标
  static calculateBollingerBands(data, period, multiplier) {
    const middle = [];
    const upper = [];
    const lower = [];
    
    for (let i = period - 1; i < data.length; i++) {
      // 计算中轨（移动平均线）
      let sum = 0;
      for (let j = 0; j < period; j++) {
        sum += data[i - j].close;
      }
      const ma = sum / period;
      middle.push(ma);
      
      // 计算标准差
      let squaredDiffSum = 0;
      for (let j = 0; j < period; j++) {
        squaredDiffSum += Math.pow(data[i - j].close - ma, 2);
      }
      const stdDev = Math.sqrt(squaredDiffSum / period);
      
      // 计算上轨和下轨
      upper.push(ma + (multiplier * stdDev));
      lower.push(ma - (multiplier * stdDev));
    }
    
    return { middle, upper, lower };
  }

  // 计算移动平均线
  static calculateMovingAverage(data, period) {
    const ma = [];
    for (let i = period - 1; i < data.length; i++) {
      let sum = 0;
      for (let j = 0; j < period; j++) {
        sum += data[i - j].close;
      }
      ma.push(sum / period);
    }
    return ma;
  }

  // 计算RSI指标
  static calculateRSI(data, period) {
    const rsi = [];
    let gains = 0;
    let losses = 0;

    // 计算前period个周期的平均收益和平均损失
    for (let i = 1; i <= period; i++) {
      const change = data[i].close - data[i - 1].close;
      if (change >= 0) {
        gains += change;
      } else {
        losses -= change;
      }
    }

    let avgGain = gains / period;
    let avgLoss = losses / period;
    let rs = avgGain / avgLoss;
    rsi.push(100 - (100 / (1 + rs)));

    // 计算后续周期的RSI
    for (let i = period + 1; i < data.length; i++) {
      const change = data[i].close - data[i - 1].close;
      let currentGain = 0;
      let currentLoss = 0;

      if (change >= 0) {
        currentGain = change;
      } else {
        currentLoss = -change;
      }

      avgGain = (avgGain * (period - 1) + currentGain) / period;
      avgLoss = (avgLoss * (period - 1) + currentLoss) / period;
      rs = avgGain / avgLoss;
      rsi.push(100 - (100 / (1 + rs)));
    }

    return rsi;
  }

  // 计算动量因子
  static calculateMomentum(data, period) {
    if (data.length < period + 1) return 0;
    const recentPrice = data[data.length - 1].close;
    const pastPrice = data[data.length - 1 - period].close;
    return ((recentPrice - pastPrice) / pastPrice) * 100;
  }

  // 计算波动性因子
  static calculateVolatility(data, period) {
    if (data.length < period) return 0;
    
    // 计算收益率序列
    const returns = [];
    for (let i = data.length - period; i < data.length; i++) {
      if (i > 0) {
        const returnVal = (data[i].close - data[i - 1].close) / data[i - 1].close;
        returns.push(returnVal);
      }
    }
    
    // 计算标准差
    const mean = returns.reduce((sum, r) => sum + r, 0) / returns.length;
    const squaredDiffs = returns.map(r => Math.pow(r - mean, 2));
    const variance = squaredDiffs.reduce((sum, sd) => sum + sd, 0) / returns.length;
    return Math.sqrt(variance) * Math.sqrt(252); // 年化波动率
  }

  // 计算成交量因子
  static calculateVolumeFactor(data, period) {
    if (data.length < period) return 0;
    
    // 计算平均成交量
    let totalVolume = 0;
    for (let i = data.length - period; i < data.length; i++) {
      totalVolume += data[i].volume;
    }
    const avgVolume = totalVolume / period;
    
    // 计算最新成交量与平均成交量的比率
    const latestVolume = data[data.length - 1].volume;
    return latestVolume / avgVolume;
  }

  // 计算价格因子（价格位置因子）
  static calculatePriceFactor(data, period) {
    if (data.length < period) return 0;
    
    // 获取周期内的最高价和最低价
    let highest = data[data.length - period].high;
    let lowest = data[data.length - period].low;
    
    for (let i = data.length - period + 1; i < data.length; i++) {
      if (data[i].high > highest) highest = data[i].high;
      if (data[i].low < lowest) lowest = data[i].low;
    }
    
    const currentPrice = data[data.length - 1].close;
    // 计算价格在周期内位置的百分比
    if (highest === lowest) return 0;
    return (currentPrice - lowest) / (highest - lowest);
  }

  // 标准化因子值
  static standardizeFactorValue(value, mean, stdDev) {
    if (stdDev === 0) return 0;
    return (value - mean) / stdDev;
  }

  // 计算综合得分
  static calculateCompositeScore(factorData, weights) {
    let score = 0;
    let totalWeight = 0;
    
    for (const [factor, weight] of Object.entries(weights)) {
      if (factorData[factor] !== undefined && weight !== 0) {
        score += factorData[factor] * weight;
        totalWeight += Math.abs(weight);
      }
    }
    
    // 归一化得分
    return totalWeight > 0 ? score / totalWeight : 0;
  }

  // 执行多因子选股策略
  static async executeMultiFactorStrategy(symbols, factorWeights, topN = 10) {
    try {
      // 动态引入 StockHistoryService 以避免循环依赖
      const StockHistoryService = require('./StockHistoryService');
      
      const stockScores = [];
      
      // 为每只股票计算因子得分
      for (const symbol of symbols) {
        try {
          // 获取历史数据
          const historicalData = await StockHistoryService.getHistoricalData(symbol, 'daily', 100);
          
          if (historicalData.length < 20) {
            console.warn(`Not enough data for ${symbol}`);
            continue;
          }
          
          // 只取最近的数据
          const recentData = historicalData.slice(-100).map(item => ({
            date: new Date(item.date),
            open: item.open,
            high: item.high,
            low: item.low,
            close: item.close,
            volume: item.volume
          }));
          
          // 计算各因子
          const factors = {
            momentum: this.calculateMomentum(recentData, 20),
            volatility: -this.calculateVolatility(recentData, 20), // 负号表示偏好低波动
            volume: this.calculateVolumeFactor(recentData, 20),
            price: this.calculatePriceFactor(recentData, 20)
          };
          
          // 计算综合得分
          const score = this.calculateCompositeScore(factors, factorWeights);
          
          stockScores.push({
            symbol: symbol,
            score: score,
            factors: factors,
            latestPrice: recentData[recentData.length - 1].close
          });
        } catch (error) {
          console.warn(`Failed to calculate factors for ${symbol}: ${error.message}`);
        }
      }
      
      // 按得分排序并返回前N只股票
      stockScores.sort((a, b) => b.score - a.score);
      
      // 添加排名信息
      const result = stockScores.slice(0, topN).map((stock, index) => ({
        ...stock,
        rank: index + 1
      }));
      
      return result;
    } catch (error) {
      console.error(`Failed to execute multi-factor strategy: ${error.message}`);
      throw new Error(`Failed to execute multi-factor strategy: ${error.message}`);
    }
  }

}

module.exports = StrategyService;